<?php

namespace backend\controllers;

use app\models\CrmCity;
use app\models\CrmProvince;
use common\helps\Tools;
use common\helps\Tree;
use Yii;
use yii\data\Pagination;
use yii\helpers\ArrayHelper;
use yii\helpers\Url;
use yii\web\Controller;

class CommonController extends Controller
{

    //项目在服务器的绝对根路径
    public $absBasePath = '';
    //项目的文件相对路径的地址，比如为/advanced/backend/web
    public $url_base = '';
    //vender的相对路径
    public $rel_vender_path = '';
    //vender的adminlte的浏览器的adminlte的相对路径
    public $adminlte = '';
    //vender的adminlte的浏览器的组建的相对路径
    public $rel_vaabc_path = '';
    public $redis;//可以为redis或者为缓存
    public $https_url = "";
    public $transaction = "";//事务

    /**
     * 权限的之前进行权限的验证，没有权限的不能访问相应的模块
     *
     * {@inheritdoc}
     *
     * @see \yii\web\Controller::beforeAction()
     */
    public function beforeAction($acUtion)
    {
        $action = Yii::$app->controller->action->id;
        $this->https_url = \Yii::$app->request->hostInfo.\Yii::$app->homeUrl;
        $result = false;
        $behaviors = $this->behaviors();
        if (isset($behaviors['filter'])){
            if (isset($behaviors['filter']['only'])){
                $result = in_array($action,$behaviors['filter']['only']);
            }
        }
        // 判断是否登录
        if (\Yii::$app->user->isGuest && !$result) {
            // 没有登录,登录,登录后,返回
            echo "没有登录！";
            exit();
        }
        date_default_timezone_set('PRC');//设置时间时区为中国
        header("Content-type:application/x-www-form-urlencoded text/html; charset=utf-8");//设置格式为utf-8
        // 指定允许其他域名访问
        header('Access-Control-Allow-Origin:'.\Yii::$app->components['allowOutHttp']);
        // 响应类型
        header("Access-Control-Allow-Methods: POST, GET, OPTIONS, PUT, DELETE");
        // 响应头设置
        header('Access-Control-Allow-Headers:X-Requested-With, origin, content-type, accept');
        // 允许带cookie
        header('Access-Control-Allow-Credentials: true');
        // 获取 redis 组件
        $this->redis = Yii::$app->cache;
        $this->parmsInit();
        return true;
    }

    /**
     * 参数的初始化
     */
    public function parmsInit()
    {
        // 初始化项目的绝对根路径，比如E:/program/phpService/www
        $this->absBasePath = Yii::$app->basePath;
        //项目的文件相对路径的地址，比如为/advanced/backend/web
        $this->url_base = Url::base();
        $last = '..' . DIRECTORY_SEPARATOR;
        $ds = DIRECTORY_SEPARATOR;
        //vender的相对路径
        $this->rel_vender_path = ($this->url_base)
            . $ds . $last . $last . 'vendor' . $ds;
        //vender的adminlte的浏览器的adminlte的相对路径
        $this->adminlte = $this->rel_vender_path . 'almasaeed2010' . $ds . 'adminlte' . $ds;
        //vender的adminlte的浏览器的组建的相对路径
        $this->rel_vaabc_path = $this->adminlte . 'bower_components' . $ds;
    }

    /**
     * 分页的功能操作
     */
    protected function pagesDo($dataProvider,$page,$limit){
        $query = $dataProvider->query;
        $countQuery = clone $query;
        $pages = new Pagination(['totalCount' => $countQuery->count()]);
        $pages->page = $page-1;
        $pages->pageSize = $limit;
        $dataProvider->pagination = $pages;
    }

    /**
     * 无论在windows还是linux里面都能实现后台运行
     * @param $cmd
     */
    function execInBackground($cmd) {
        if (substr(php_uname(), 0, 7) == "Windows"){
            $timer =popen("start /B ". $cmd , "r");
            usleep(5);
            pclose($timer);
        }
        else {
            exec($cmd . " > /dev/null &");
        }
    }

    /**
     * 查询号码归属地，返回json字符串
     */
    function actionSearchTelephoneAssignment($res){
        $result = "";
        $city = new CrmCity();
        //查到城市
        $cityRes = $city->find()->select("ProID,CityID,CityName,PYJM,PhoneArea")->andFilterWhere(['like', 'MobileArea', $res])->asArray()->one();
        $result['city'] = $cityRes;
        $province = new CrmProvince();
        //通过城市查到省份
        $provinceRes = $province->find()->select("ProID,ProName,PYJM,WBJM,ProvCapital")->andWhere(['ProID'=>$cityRes['ProID']])->asArray()->one();
        $result['province'] = $provinceRes;
        return $result;
    }

    /**
     * 共用的拿到列表的方法
     * @param $model
     * @param $type 文件类型
     * @param $page 如果post方式的话就要提交到这里 , page=1,limit=-1是查询所有
     * @param $limit 如果post方式的话就要提交到这里，
     * @return string
     */
    public function getList($model,$page="",$limit="",$condition=null,$params=null)
    {
        try {
            $page = $page==""?(isset($_GET['page'])?$_GET['page']:(isset($_POST['page'])?$_POST['page']:0)):$page;
            $limit = $limit==""?(isset($_GET['limit'])?$_GET['limit']:(isset($_POST['limit'])?$_POST['limit']:0)):$limit;
            if (empty($condition)){
                $all = ArrayHelper::toArray($model->find()->select("*")->limit($limit)->offset(($limit)*($page-1))->all());
                $count = $model->find()->select("*")->count();
            }else{
                $all = ArrayHelper::toArray($model->find()->select("*")->limit($limit)->offset(($limit)*($page-1))->andWhere($condition)->all());
                $count = $model->find()->select("*")->andWhere($condition)->count();
            }
            return $this->actionLayData($count,$all,0,"",$page,$params);
        } catch (\Exception $e) {
            Tools::l($e);
        }
    }

    public function getSearchList($model,$params)
    {
        try {
            $lists = $model->search($params);
            $limit = is_set($_POST,"limit");
            $offset = is_set($_POST,"limit")*(is_set($_POST,"page")-1);
            $lists->query->limit($limit)->offset($offset);
            return $this->actionLayData($lists->count,$lists->query->asArray()->all(),0,'',is_set($_POST,"page"));
        } catch (\Exception $e) {
            Tools::l($e);
        }
    }

    /**
     * 共用的文件列表的方法
     * @param $model
     * @param $type 文件类型
     * @return string
     */
    public function getFileList($model,$type=null,$params=null){
        try{
            $page = (isset($_GET['page'])?$_GET['page']:(isset($_POST['page'])?$_POST['page']:0));
            $limit = (isset($_GET['limit'])?$_GET['limit']:(isset($_POST['limit'])?$_POST['limit']:0));
            if (empty($type)){
                $all = $model->find()->select("*")->limit($limit)->offset(($limit)*($page-1))->asArray()->all();
                $count = $model->find()->select("*")->count();
            }else{
                $all = $model->find()->select("*")->limit($limit)->offset(($limit)*($page-1))->andWhere(['type'=>$type])->asArray()->all();
                $count = $model->find()->select("*")->andWhere(['type'=>$type])->count();
            }
            return $this->actionLayData($count,$all,0,"",$page,$params);
        }catch (\Exception $e){
            Tools::l($e);
        }
    }

    /**
     * 下载文件，传递文件的本地的文件路径
     * @param $filename
     */
    function downfile($filename)
    {
        $file = pathinfo($filename);
        Header( "Content-type:  application/octet-stream ");
        Header( "Accept-Ranges:  bytes ");
        Header( "Accept-Length: " .filesize($filename));
        header( "Content-Disposition:  attachment;  filename= ".$file["basename"]);
        echo file_get_contents($filename);
        readfile($filename);
    }

    /**
     * 用来返回空的lay需要解析的数据
     * @return string
     */
    public function actionNullLayData($msg="无数据"){
        $res = [];
        $res['code'] = 0;
        $res['msg'] = $msg;
        $res['count'] = 0;
        $res['data'] = [''];
        return json_encode($res);
    }

    /**
     * 用来返回空的lay需要解析的数据，精简版
     * @return string
     */
    public function actionNullLayData_(){
        return '{"code":0,"page":'.(isset($_GET['page'])?$_GET['page']:is_set($_POST,'page')).',"data":[""]}';
    }

    /**
     * 用来返 lay需要解析的数据
     * @param $count 数据的总数
     * @param $data 数据
     * @param int $code 返回代码
     * @param string $msg 返回没有数据的时候的信息
     * @return string
     */
    public function actionLayData($count,$data,$code=0,$msg="",$page=1,$params=""){
        $res = [];
        $res['code'] = $code;
        $res['count'] = $count;
        $res['page'] = $page;
        $res['data'] = $data;
        $res['msg'] = $msg;
        if (!empty($params)){
            $res['params'] = $params;
        }
        return json_encode($res,JSON_UNESCAPED_SLASHES);
    }

    /**
     * 用来返回 element-ui需要解析的数据
     */
    public function actionElementData($res){
        $r = [];
        foreach ($res as $k=>$v){//使数据符合前端element-ui的格式
            $r[$k] = $v;
            $r[$k]['children'] = [];
        }
        return $r;
    }

    /**
     * 将数据进行统一处理，然后传到前端，让前端更能够识别，采用统一的模式
     * @param $data 传递的数据
     * @param $code 传递的代码 0代表失败；1代表成功
     * @return string
     */
    public function dealFD($data,$code=1){
        $res['data'] = $data;
        $res['res'] = $code;
        return json_encode($res,true);
    }
    /**
     * 开启事务
     */
    public function startT(){
        $this->transaction = \Yii::$app->getDb()->beginTransaction();//开启事务
        return $this->transaction;
    }
    /**
     * 生成element-ui需要的树形数组
     */
    public function getElementTree($arr,$config_){
        $obj = new Tree();
        //设置节点名称,默认为id,pid,child,如果是默认的,不用设置
        $config = $config_==""?array(
            'key'  => 'id', //主键
            'pKey' => 'parent_id', //主键父级名称
            'child'=> 'children'//子节点的名称
        ):$config_;
        $obj->setConfig($config);
        $obj->setArrSource($arr);
        //通过排序,保证子节点出现在父节点的前面,如果子节点在父节点前面,不用调用此方法
        $obj->sortArr();
        $result = $obj->getTree();
        sort($result);
        return $result;
    }
}